<?php
/**
 * Created by PhpStorm.
 * User: Korbin
 * Date: 2018/11/10
 * Time: 13:45
 */

namespace app\script\command;

use app\common\model\DataComment;
use app\common\model\DataVideo;
use app\common\model\Job;
use think\console\Input;
use think\console\input\Option;
use think\console\Output;

class TiktokComment extends Base
{
    private $listKey = 'comments';//获取数据区域

    private $host = 'https://api2.musical.ly/aweme/v1/comment/list/?aid=1233&count=20';



    /**
     * 设置执行名称及配置传入参数、脚本描述
     */
    protected function configure()
    {
        $this->setName('tiktokVideoComment')
            ->addOption('job', 'j', Option::VALUE_OPTIONAL)
            ->setDescription('Run all the time');
    }

    /*********************公用验证部分************************************/
    /*
     * 执行脚本任务
     *
     * @param Input $input
     * @param Output $output
     */
    protected function execute(Input $input, Output $output)
    {
        $job = $input->getOption('job');
        if (empty($job)) {
            $output->writeln('请传入执行任务ID：' . date('Y-m-d H:i:s'));
            exit();
        }

        $output->writeln('脚本开始：' . date('Y-m-d H:i:s'));
        $jobModel = new Job();
        $jobInfo = $jobModel->where(['id' => $job])->find();//获取任务配置信息
        if (empty($jobInfo)) {
            $output->writeln('任务ID不存在：' . date('Y-m-d H:i:s'));
            exit();
        } else {
            $jobInfo = $jobInfo->toArray();
        }
//        $this->redis->hSet('job_status',$job,1);
        $jobRedisInfo = $this->redis->hGet('jobHash', $job);//获取任务redis记录
        if (empty($jobRedisInfo)) {
            $jobRedisData = [
                'planned_quantity' => $jobInfo['planned_quantity'],
                'real_quantity' => (empty($jobInfo['real_quantity']) ? 0 : $jobInfo['real_quantity']),
                'shortvideo_num' => (empty($jobInfo['shortvideo_num']) ? 0 : $jobInfo['shortvideo_num']),
                'smallvideo_num' => (empty($jobInfo['smallvideo_num']) ? 0 : $jobInfo['smallvideo_num']),
                'finsh_time' => '',
            ];
        } else {
            $jobRedisData = json_decode($jobRedisInfo, true);
            $jobRedisData['planned_quantity'] = $jobInfo['planned_quantity'];
        }
        $video = new DataVideo();
        //开始循环执行采集任务
        while (true) {
            //采集开始执行验证采集开关是否打开
            $jobStatus = $this->redis->hGet('job_status', $job);
            if ($jobStatus != 1) {
                break;//采集开关关闭时跳出循环结束脚本执行
            }
            /*$test['id']='fff513cd-3589-4c3e-b72e-28d1cf1a8f40';
            $test['paltform_vid']='vivashow_85dc3506e9bb4281a19e28eb04007553';
            $videoList[]=$test;*/
            $videoList=[];
            $where['paltform']=$jobInfo['platform'];
            $where['lang'] = 2;
//            $where['paltform']='TikTok';
            $where['comment_status']=0;
            $videoList=$video->field('paltform_vid,id')->where($where)->limit(0,10)->select();
            foreach($videoList as $videoVal){
                for($i=0;$i<5;$i++){
                    $result = $this->getApiData($i,$videoVal['paltform_vid']);//获取采集源结果
                    //验证是否有相应的采集数据
                    if (is_array($result) && array_key_exists($this->listKey, $result)) {
                        $lists = $result[$this->listKey];
                    } else {
                        $output->writeln($this->getName().'采集源服务器出错或找不到采集信息！'.date('Y-m-d H:i:s'));
                        break;
                    }

                    //开始拼装数据
                    $insertData = [];
                    if (!empty($lists)) {
                        $this->createData($lists, $jobInfo, $jobRedisData, $insertData,$videoVal);//对源数据进行对应入库
                        if (!empty($insertData)) {
                            //当实际采集数据大于等于计划采集数据量时设置redis开关值
                            if (($jobRedisData['planned_quantity'] - $jobRedisData['real_quantity']) <= 0) {
                                $this->redis->hSet('job_status', $job, 2);//正常完成值为2
                                $jobRedisData['finsh_time'] = date('Y-m-d H:i:s');//正常完成时间记录
                                $jobModel->save(['job_status'=>2,'status_time'=>date('Y-m-d H:i:s')],['id'=>$job]);
                            }
                            $this->redis->hSet('jobHash', $job, json_encode($jobRedisData));
                            $output->writeln('【'.$this->getName().'采集成功】本次采集入库数据条数为【' . count($insertData) . '】'.date('Y-m-d H:i:s'));
                        } else {
                            $output->writeln('【'.$this->getName().'执行成功】本次采集无符合要求的数据入库!'.date('Y-m-d H:i:s'));
                        }
                    }
                }
                $video->where(['id'=>$videoVal['id']])->update(['comment_status'=>1]);
            }
            //间隔随机时间
            $sleep = rand(10, 20);
            sleep($sleep);
        }

        $output->writeln($this->getName().'任务执行完毕：' . date('Y-m-d H:i:s'));
    }
    /*********************公用验证部分************************************/

    /**
     * 组装url进行数据获取
     *
     * @return mixed
     */
    private function getApiData($i=0,$awemeId)
    {
        $cursor=$i*20;
        $url = $this->host;
        $url.="&aweme_id=".$awemeId."&cursor=".$cursor;
        //$url='http://api2.musical.ly/aweme/v1/comment/list/?aweme_id=6603700198877170950&aid=1233&count=20&cursor=20';
        //$url='http://api.tiktokv.com/aweme/v1/feed/?type=0&max_cursor=0&count=6&aid=1180';
        $header=[
            'cache-control: no-cache',
            'User-Agent: PostmanRuntime/7.4.0',
            'Accept: */*',
            'content-length: 0',
            'Connection: keep-alive',
        ];
        $result = curl_post_formurlen($url,[],$header);
        $result = json_decode($result, true);
        //dump($result);die;
        return $result;
    }

    /**
     * 采集数据拼装入库
     *
     * @param $lists
     * @param $jobInfo
     * @param $jobRedisData
     * @param $insertData
     */
    private function createData($lists, $jobInfo, &$jobRedisData, &$insertData,$videoVal)
    {
        $video = new DataComment();
        foreach ($lists as $val) {
            //判断是否 已经存在
            $isExist = $video->field('id')->where([
                'comment_id' => $val['cid']
            ])->find();
            if ($isExist) {
                continue;
            }
            $data = [];
            $data['video_id']=$videoVal['id'];
            $data['parent_id']='';
            $data['parent_ids']='';
            $data['comment_uid']=isset($val['user']['uid'])?$val['user']['uid']:'';//评论者
            $data['comment_uname']=isset($val['user']['nickname'])?$val['user']['nickname']:'';//评论用户昵称
            $data['comment_uhead']=isset($val['user']['avatar_thumb']['url_list'][0])?$val['user']['avatar_thumb']['url_list'][0]:'';//评论用户头像
            $data['thumb_num']=0;//评论点赞数
            $data['comment_content']=$val['text'];//评论内容
            $data['comment_time']=date("Y-m-d H:i:s",$val['create_time']);//评论时间
            $data['sort']=0;//排序


            $data['create_by'] = $jobInfo['create_by'];
            $data['create_date'] = date('Y-m-d H:i:s');
            $data['update_by'] = $jobInfo['update_by'];
            $data['update_date'] = date('Y-m-d H:i:s');

            $data['comment_id'] = $val['cid'];
            $data['id']=com_create_guid();//生成唯一UUID

            $insertData[] = $data;

            $jobRedisData['real_quantity'] += 1;//实际采集数量+1
        }
        $video->isUpdate(false)->saveAll($insertData, false);
    }

    /**
     * 验证采集数据是否符合条件
     *
     * @param $data
     * @param $jobInfo
     * @return bool
     */
    private function validateNum($data,$jobInfo){
        $res = true;
        $keys = array_keys($data);
        foreach ($keys as $val){
            if($jobInfo[$val]>$data[$val]){
                $res = false;
                break;
            }
        }
        return $res;
    }
}